import { useEffect, useState, forwardRef, useImperativeHandle } from 'react';
import { Tree, Empty, Spin, message } from 'antd';
import { DownOutlined } from '@ant-design/icons';
import { useApp, InbizIcon } from '@inbiz/utils';
import { getMessage } from '@inbiz/react';
import { getPageTree, getFormPageTree } from '../service';
import { getTreeCurrentData, getQueryParams } from '../utils';
import '../style.less';

const { TreeNode } = Tree;

const TreeList = forwardRef((props: any, ref) => {
    const { searchText, siteInfo, setSelectedRow, queryRef } = props;
    const [loading, setLoading] = useState(true);
    const [treeData, setTreeData] = useState<any[]>([]);
    const [allData, setAllData] = useState<any[]>([]);
    const [selectedKeys, setSelectedKeys] = useState<any>(null);
    const [expandedKeys, setExpandedKeys] = useState<any[]>([]);
    const appInfo: any = useApp();

    const onSelect = (selectedKeys: string[], e: any) => {
        queryRef?.current?.setSelectedRowKeys([]);
        if (e?.node?.icon?.props?.type == 'icon-fenzu') {
            if (expandedKeys?.includes(selectedKeys?.[0])) {
                setExpandedKeys(expandedKeys?.filter((item) => item != selectedKeys?.[0]));
            } else {
                setExpandedKeys([...expandedKeys, ...selectedKeys]);
            };
        } else {
            if (selectedKeys?.length != 0) {
                const _currentRow = getTreeCurrentData(selectedKeys?.[0], allData);
                setSelectedRow(_currentRow);
                setSelectedKeys(selectedKeys);
                const isApp = selectedKeys?.[0] == appInfo?.OutId;
                const _isForm = !!_currentRow?.IsWf;
                queryRef?.current?.queryForm?.resetFields();
                if (queryRef?.current?.currentType == '1') {
                    queryRef?.current?.queryForm?.setFieldValue('componentLanguageType', 0);
                };
                queryRef?.current?.getLangData(getQueryParams(_isForm, queryRef?.current?.currentType, isApp, _currentRow, siteInfo));
            };
        };
    };

    const init = () => {
        setSelectedKeys([]);
        setSelectedRow(null);
        setTreeData([]);
        setAllData([]);
    };

    const getTreeData = async (isForm: boolean, siteInfo: any, callback?: (dataVersionId: string) => void) => {
        setLoading(true);
        try {
            setExpandedKeys([]);
            const results = isForm ? await getFormPageTree() : await getPageTree({
                siteOutId: siteInfo?.OutId || '',
                dataVersionId: siteInfo?.DataVersionId || '',
                appId: appInfo?.AppId || '',
            });
            if (results) {
                const _data = [
                    {
                        IsApp: true,
                        Name: appInfo?.Name,
                        OutId: appInfo?.OutId,
                        DataVersionId: isForm ? results?.[0]?.DataVersionId : appInfo?.DataVersionId,
                        IsWf: isForm ? true : false,
                    },
                    ...results
                ];
                const _row = _data?.find((item) => item?.OutId == appInfo?.OutId);
                setSelectedKeys([appInfo?.OutId]);
                setSelectedRow(_row);
                setTreeData(_data);
                setAllData(_data);
                callback && callback(isForm ? results?.[0]?.DataVersionId : '');
            } else {
                init();
            };
            setLoading(false);
        } catch (error: any) {
            message.error(error);
            init();
            setLoading(false);
        };
    };

    const dispalyTreeName = (name: string) => {
        if (searchText) {
            const index = name.indexOf(searchText);
            if (index > -1) {
                return <span>{name.slice(0, index)}
                    <span style={{ color: 'var(--inbiz-color-danger)' }}>
                        {name.slice(index, searchText.length + index)}
                    </span>
                    {name.slice(searchText.length + index)}
                </span>
            } else {
                return name;
            };
        } else {
            return name;
        };
    };

    const renderTree = (_treeData?: any) => {
        return (_treeData || treeData)?.map((item: any) => {
            if (item?.IsApp) {
                return (
                    <TreeNode
                        key={item?.OutId}
                        icon={<InbizIcon type={'icon-shouye1'} />}
                        title={dispalyTreeName(getMessage(item?.Name))}
                        className='app-node'
                    />
                )
            } else {
                if (item?.IsGroup || item?.Children && item?.Children?.length > 0) {
                    return (
                        <TreeNode
                            key={item?.OutId}
                            icon={<InbizIcon type={item?.IsGroup ? 'icon-fenzu' : 'icon-yemian'} />}
                            title={dispalyTreeName(getMessage(item?.Name))}
                        >
                            {renderTree(item?.Children)}
                        </TreeNode>
                    )
                } else {
                    return (
                        <TreeNode
                            key={item?.OutId}
                            icon={<InbizIcon type={'icon-yemian'} />}
                            title={dispalyTreeName(getMessage(item?.Name))}
                        />
                    )
                };
            }
        });
    };

    const filterGroupData = (group: any) => {
        if (group?.Children?.length > 0) {
            for (let i = 0; i < group?.Children?.length; i++) {
                if (group?.Children[i]?.Name?.indexOf(searchText) != -1) {
                    const _expandedKeys = Array.from(new Set([...expandedKeys, group?.OutId]));
                    setTimeout(() => {
                        setExpandedKeys(_expandedKeys);
                    }, 0)
                    return true;
                } else {
                    for (let j = 0; j < group?.Children[i]?.Children.length; j++) {
                        if (group?.Children[i]?.Children[j]?.Name?.indexOf(searchText) != -1) {
                            const _expandedKeys = Array.from(new Set([...expandedKeys, group?.Children[i]?.OutId, group?.OutId]));
                            setTimeout(() => {
                                setExpandedKeys(_expandedKeys);
                            }, 0)
                            return true;
                        };
                    };
                };
            };
        };
    };

    const filterTreeData = () => {
        const _treeData = allData?.filter((item: any) => {
            if (item?.IsGroup) {
                if (item?.Name?.indexOf(searchText) != -1) {
                    if (item?.Children?.length > 0) {
                        filterGroupData(item);
                    };
                    return true;
                } else {
                    return filterGroupData(item);
                };
            } else {
                if (item?.Name?.indexOf(searchText) != -1) {
                    return true;
                };
            };
        });
        return _treeData;
    };

    useEffect(() => {
        if (searchText) {
            const _treeData = filterTreeData();
            setTreeData(_treeData);
        } else {
            setTreeData(allData);
            setExpandedKeys([]);
        };
    }, [searchText]);

    useImperativeHandle(ref, () => {
        return {
            getTreeData,
        };
    });

    return (
        <div className={`inbiz-lang-manage-left-tree-list-wrapper ${siteInfo ? 'notForm' : ''}`}>
            <Spin spinning={loading}>
                <Tree
                    onSelect={onSelect}
                    expandedKeys={expandedKeys}
                    selectedKeys={selectedKeys}
                    onExpand={(expandedKeys: any) => {
                        setExpandedKeys(expandedKeys || []);
                    }}
                    showIcon
                    switcherIcon={<DownOutlined />}
                >
                    {renderTree()}
                </Tree>
                {(treeData.length < 1 && !loading) && <div className='inbiz-lang-manage-left-tree-list-empty'>
                    <Empty image={Empty.PRESENTED_IMAGE_SIMPLE} />
                </div>}
            </Spin>
        </div>
    )
});

export default TreeList;